package com.dm.utils;

import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.text.SimpleDateFormat;
import java.util.Date;

import android.content.Context;
import android.telephony.TelephonyManager;

import com.dm.logger.Logger;

/**
 * Get phone info, such as IMEI,IMSI,Number,Sim State, etc.
 *
 * <uses-permission android:name="android.permission.READ_PHONE_STATE"/>
 *
 * @author MaTianyu
 * @date 2014-09-25
 */
public class DeviceUtil {

	private static final String TAG = DeviceUtil.class.getSimpleName();

	/**
	 * IMSI是国际移动用户识别码的简称(International Mobile Subscriber Identity)
	 * IMSI共有15位，其结构如下： MCC+MNC+MIN MCC：Mobile Country Code，移动国家码，共3位，中国为460;
	 * MNC:Mobile NetworkCode，移动网络码，共2位 在中国，移动的代码为电00和02，联通的代码为01，电信的代码为03
	 * 合起来就是（也是Android手机中APN配置文件中的代码）： 中国移动：46000 46002 中国联通：46001 中国电信：46003
	 * 举例，一个典型的IMSI号码为460030912121001
	 */
	public static String getIMSI(Context context) {
		TelephonyManager telephonyManager = (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
		String IMSI = telephonyManager.getSubscriberId();
		Logger.i(TAG, " IMSI：" + IMSI);
		return IMSI;
	}

	/**
	 * IMEI是International Mobile Equipment Identity （国际移动设备标识）的简称
	 * IMEI由15位数字组成的”电子串号”，它与每台手机一一对应，而且该码是全世界唯一的 其组成为： 1.
	 * 前6位数(TAC)是”型号核准号码”，一般代表机型 2. 接着的2位数(FAC)是”最后装配号”，一般代表产地 3.
	 * 之后的6位数(SNR)是”串号”，一般代表生产顺序号 4. 最后1位数(SP)通常是”0″，为检验码，目前暂备用
	 */
	public static String getIMEI(Context context) {
		TelephonyManager telephonyManager = (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
		String IMEI = telephonyManager.getDeviceId();
		Logger.i(TAG, " IMEI：" + IMEI);
		return IMEI;
	}

	/**
	 * Print telephone info.
	 */
	public static String printTelephoneInfo(Context context) {
		Date date = new Date(System.currentTimeMillis());
		SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
		String time = dateFormat.format(date);
		StringBuilder sb = new StringBuilder();
		sb.append("_______ 手机信息  ").append(time).append(" ______________");
		TelephonyManager tm = (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
		String IMSI = tm.getSubscriberId();
		// IMSI前面三位460是国家号码，其次的两位是运营商代号，00、02是中国移动，01是联通，03是电信。
		String providerName = null;
		if (IMSI != null) {
			if (IMSI.startsWith("46000") || IMSI.startsWith("46002")) {
				providerName = "中国移动";
			} else if (IMSI.startsWith("46001")) {
				providerName = "中国联通";
			} else if (IMSI.startsWith("46003")) {
				providerName = "中国电信";
			}
		}
		sb.append(providerName).append("  手机号：").append(tm.getLine1Number()).append(" IMSI是：").append(IMSI);
		sb.append("\nDeviceID(IMEI)       :").append(tm.getDeviceId());
		sb.append("\nDeviceSoftwareVersion:").append(tm.getDeviceSoftwareVersion());
		sb.append("\ngetLine1Number       :").append(tm.getLine1Number());
		sb.append("\nNetworkCountryIso    :").append(tm.getNetworkCountryIso());
		sb.append("\nNetworkOperator      :").append(tm.getNetworkOperator());
		sb.append("\nNetworkOperatorName  :").append(tm.getNetworkOperatorName());
		sb.append("\nNetworkType          :").append(tm.getNetworkType());
		sb.append("\nPhoneType            :").append(tm.getPhoneType());
		sb.append("\nSimCountryIso        :").append(tm.getSimCountryIso());
		sb.append("\nSimOperator          :").append(tm.getSimOperator());
		sb.append("\nSimOperatorName      :").append(tm.getSimOperatorName());
		sb.append("\nSimSerialNumber      :").append(tm.getSimSerialNumber());
		sb.append("\ngetSimState          :").append(tm.getSimState());
		sb.append("\nSubscriberId         :").append(tm.getSubscriberId());
		sb.append("\nVoiceMailNumber      :").append(tm.getVoiceMailNumber());

		Logger.i(TAG, sb.toString());
		return sb.toString();
	}

	// ///_________________ 双卡双待系统IMEI和IMSI方案（see more on
	// http://benson37.iteye.com/blog/1923946）

	/**
	 * 双卡双待神机IMSI、IMSI、PhoneType信息 <uses-permission
	 * android:name="android.permission.READ_PHONE_STATE"/>
	 */
	public static class TeleInfo {
		public String imsi_1;
		public String imsi_2;
		public String imei_1;
		public String imei_2;
		public int phoneType_1;
		public int phoneType_2;

		@Override
		public String toString() {
			return "TeleInfo{" + "imsi_1='" + imsi_1 + '\'' + ", imsi_2='" + imsi_2 + '\'' + ", imei_1='" + imei_1 + '\'' + ", imei_2='" + imei_2 + '\'' + ", phoneType_1=" + phoneType_1 + ", phoneType_2=" + phoneType_2 + '}';
		}
	}

	/**
	 * MTK Phone.
	 *
	 * 获取 MTK 神机的双卡 IMSI、IMSI 信息
	 */
	public static TeleInfo getMtkTeleInfo(Context context) {
		TeleInfo teleInfo = new TeleInfo();
		try {
			Class<?> phone = Class.forName("com.android.internal.telephony.Phone");

			Field fields1 = phone.getField("GEMINI_SIM_1");
			fields1.setAccessible(true);
			int simId_1 = (Integer) fields1.get(null);

			Field fields2 = phone.getField("GEMINI_SIM_2");
			fields2.setAccessible(true);
			int simId_2 = (Integer) fields2.get(null);

			TelephonyManager tm = (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
			Method getSubscriberIdGemini = TelephonyManager.class.getDeclaredMethod("getSubscriberIdGemini", int.class);
			String imsi_1 = (String) getSubscriberIdGemini.invoke(tm, simId_1);
			String imsi_2 = (String) getSubscriberIdGemini.invoke(tm, simId_2);
			teleInfo.imsi_1 = imsi_1;
			teleInfo.imsi_2 = imsi_2;

			Method getDeviceIdGemini = TelephonyManager.class.getDeclaredMethod("getDeviceIdGemini", int.class);
			String imei_1 = (String) getDeviceIdGemini.invoke(tm, simId_1);
			String imei_2 = (String) getDeviceIdGemini.invoke(tm, simId_2);

			teleInfo.imei_1 = imei_1;
			teleInfo.imei_2 = imei_2;

			Method getPhoneTypeGemini = TelephonyManager.class.getDeclaredMethod("getPhoneTypeGemini", int.class);
			int phoneType_1 = (Integer) getPhoneTypeGemini.invoke(tm, simId_1);
			int phoneType_2 = (Integer) getPhoneTypeGemini.invoke(tm, simId_2);
			teleInfo.phoneType_1 = phoneType_1;
			teleInfo.phoneType_2 = phoneType_2;
		} catch (Exception e) {
			e.printStackTrace();
		}
		Logger.i(TAG, "MTK: " + teleInfo);
		return teleInfo;
	}

	/**
	 * MTK Phone.
	 *
	 * 获取 MTK 神机的双卡 IMSI、IMSI 信息
	 */
	public static TeleInfo getMtkTeleInfo2(Context context) {
		TeleInfo teleInfo = new TeleInfo();
		try {
			TelephonyManager tm = (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
			Class<?> phone = Class.forName("com.android.internal.telephony.Phone");
			Field fields1 = phone.getField("GEMINI_SIM_1");
			fields1.setAccessible(true);
			int simId_1 = (Integer) fields1.get(null);
			Field fields2 = phone.getField("GEMINI_SIM_2");
			fields2.setAccessible(true);
			int simId_2 = (Integer) fields2.get(null);

			Method getDefault = TelephonyManager.class.getMethod("getDefault", int.class);
			TelephonyManager tm1 = (TelephonyManager) getDefault.invoke(tm, simId_1);
			TelephonyManager tm2 = (TelephonyManager) getDefault.invoke(tm, simId_2);

			String imsi_1 = tm1.getSubscriberId();
			String imsi_2 = tm2.getSubscriberId();
			teleInfo.imsi_1 = imsi_1;
			teleInfo.imsi_2 = imsi_2;

			String imei_1 = tm1.getDeviceId();
			String imei_2 = tm2.getDeviceId();
			teleInfo.imei_1 = imei_1;
			teleInfo.imei_2 = imei_2;

			int phoneType_1 = tm1.getPhoneType();
			int phoneType_2 = tm2.getPhoneType();
			teleInfo.phoneType_1 = phoneType_1;
			teleInfo.phoneType_2 = phoneType_2;
		} catch (Exception e) {
			e.printStackTrace();
		}
		Logger.i(TAG, "MTK2: " + teleInfo);
		return teleInfo;
	}

	/**
	 * Qualcomm Phone. 获取 高通 神机的双卡 IMSI、IMSI 信息
	 */
	public static TeleInfo getQualcommTeleInfo(Context context) {
		TeleInfo teleInfo = new TeleInfo();
		try {
			TelephonyManager tm = (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
			Class<?> simTMclass = Class.forName("android.telephony.MSimTelephonyManager");
			Object sim = context.getSystemService("phone_msim");
			int simId_1 = 0;
			int simId_2 = 1;

			Method getSubscriberId = simTMclass.getMethod("getSubscriberId", int.class);
			String imsi_1 = (String) getSubscriberId.invoke(sim, simId_1);
			String imsi_2 = (String) getSubscriberId.invoke(sim, simId_2);
			teleInfo.imsi_1 = imsi_1;
			teleInfo.imsi_2 = imsi_2;

			Method getDeviceId = simTMclass.getMethod("getDeviceId", int.class);
			String imei_1 = (String) getDeviceId.invoke(sim, simId_1);
			String imei_2 = (String) getDeviceId.invoke(sim, simId_2);
			teleInfo.imei_1 = imei_1;
			teleInfo.imei_2 = imei_2;

			Method getDataState = simTMclass.getMethod("getDataState");
			int phoneType_1 = tm.getDataState();
			int phoneType_2 = (Integer) getDataState.invoke(sim);
			teleInfo.phoneType_1 = phoneType_1;
			teleInfo.phoneType_2 = phoneType_2;
		} catch (Exception e) {
			e.printStackTrace();
		}
		Logger.i(TAG, "Qualcomm: " + teleInfo);
		return teleInfo;
	}

	/**
	 * Spreadtrum Phone.
	 *
	 * 获取 展讯 神机的双卡 IMSI、IMSI 信息
	 */
	public static TeleInfo getSpreadtrumTeleInfo(Context context) {
		TeleInfo teleInfo = new TeleInfo();
		try {

			TelephonyManager tm1 = (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
			String imsi_1 = tm1.getSubscriberId();
			String imei_1 = tm1.getDeviceId();
			int phoneType_1 = tm1.getPhoneType();
			teleInfo.imsi_1 = imsi_1;
			teleInfo.imei_1 = imei_1;
			teleInfo.phoneType_1 = phoneType_1;

			Class<?> phoneFactory = Class.forName("com.android.internal.telephony.PhoneFactory");
			Method getServiceName = phoneFactory.getMethod("getServiceName", String.class, int.class);
			getServiceName.setAccessible(true);
			String spreadTmService = (String) getServiceName.invoke(phoneFactory, Context.TELEPHONY_SERVICE, 1);

			TelephonyManager tm2 = (TelephonyManager) context.getSystemService(spreadTmService);
			String imsi_2 = tm2.getSubscriberId();
			String imei_2 = tm2.getDeviceId();
			int phoneType_2 = tm2.getPhoneType();
			teleInfo.imsi_2 = imsi_2;
			teleInfo.imei_2 = imei_2;
			teleInfo.phoneType_2 = phoneType_2;

		} catch (Exception e) {
			e.printStackTrace();
		}
		Logger.i(TAG, "Spreadtrum: " + teleInfo);
		return teleInfo;
	}
}
